Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > comp.lang.objective-c > #204 > unrolled thread
| Started by | modelling.data@gmail.com |
|---|---|
| First post | 2015-11-14 09:14 -0800 |
| Last post | 2015-11-15 00:12 -0800 |
| Articles | 7 — 2 participants |
Back to article view | Back to comp.lang.objective-c
Row of objects: for loop creates only 2 rows out of 5 modelling.data@gmail.com - 2015-11-14 09:14 -0800
Re: Row of objects: for loop creates only 2 rows out of 5 "Pascal J. Bourguignon" <pjb@informatimago.com> - 2015-11-14 22:24 +0100
Re: Row of objects: for loop creates only 2 rows out of 5 modelling.data@gmail.com - 2015-11-15 00:10 -0800
Re: Row of objects: for loop creates only 2 rows out of 5 "Pascal J. Bourguignon" <pjb@informatimago.com> - 2015-11-15 21:40 +0100
Re: Row of objects: for loop creates only 2 rows out of 5 modelling.data@gmail.com - 2015-11-17 07:30 -0800
Re: Row of objects: for loop creates only 2 rows out of 5 "Pascal J. Bourguignon" <pjb@informatimago.com> - 2015-11-14 22:47 +0100
Re: Row of objects: for loop creates only 2 rows out of 5 modelling.data@gmail.com - 2015-11-15 00:12 -0800
| From | modelling.data@gmail.com |
|---|---|
| Date | 2015-11-14 09:14 -0800 |
| Subject | Row of objects: for loop creates only 2 rows out of 5 |
| Message-ID | <fb748a8e-9beb-4d63-866c-11dc8dc55b18@googlegroups.com> |
Hello!
I have written a post regarding the same program.
I have an issue with the easiest part of it, and I don't see
my mistake: the for loop in the BRICKS FUNCTION doesn't create
5 rows of bricks, but only 2, albeit the amount of columns is correct
(all bricks are perfectly aligned within 10 columns). The program
prints out only 2 rows of bricks.
I understand that this program implies the availability of Stanford
Portable Library, and that without this library you can't compile
the program. But I hope that because all functions have descriptive
names, you will understand what the desired outcome.
If "=" is a brick, then the outcome should look like this:
= = = = = = = = = =
= = = = = = = = = =
= = = = = = = = = =
= = = = = = = = = =
= = = = = = = = = =
I get only first two rows out of five.
// standard libraries
#include <stdio.h>
// Stanford Portable Library
#include <spl/gevents.h>
#include <spl/gobjects.h>
#include <spl/gwindow.h>
// height and width of game's window in pixels
#define HEIGHT 600
#define WIDTH 400
// number of rows of bricks
#define ROWS 5
// number of columns of bricks
#define COLS 10
// horizontal space between bricks
#define HS 10
#define VS 10
// brick size
#define BRWIDTH 29
#define BRHEIGHT 15
void initBricks(GWindow window);
int main(void)
{
// instantiate window
GWindow window = newGWindow(WIDTH, HEIGHT);
initBricks(window);
return 0;
}
/** BRICKS FUNCTION **/
void initBricks(GWindow window)
{
double x = 10;
double y = VS * 5;
for (int i = 0; i < ROWS; i++)
{
for (int j = 0; j < COLS; j++)
{
GRect brick = newGRect(x, y, BRWIDTH, BRHEIGHT);
add(window, brick);
x = x + BRWIDTH + HS;
}
x = 10;
y = BRHEIGHT + VS;
}
}
Thank you!
[toc] | [next] | [standalone]
| From | "Pascal J. Bourguignon" <pjb@informatimago.com> |
|---|---|
| Date | 2015-11-14 22:24 +0100 |
| Message-ID | <87twoo1dg4.fsf@kuiper.lan.informatimago.com> |
| In reply to | #204 |
modelling.data@gmail.com writes:
> Hello!
>
> I have written a post regarding the same program.
You should provide a makefile along with your program! Otherwise, how
can we know how to compile it, what options you used, and how to run it?
Here is the makefile I used, but if yours is different, then obviously
we will have different results, and I won't be able to debug your
program.
> I have an issue with the easiest part of it, and I don't see
> my mistake: the for loop in the BRICKS FUNCTION doesn't create
> 5 rows of bricks, but only 2, albeit the amount of columns is correct
> (all bricks are perfectly aligned within 10 columns). The program
> prints out only 2 rows of bricks.
Indeed, it does. However, I remark that it exits and the window
displayed by the JavaBackEnd stays up.
Therefore I would infer that there's a bufferization problem: you have
to leave the connection open enough time for the data to be actually
sent and received by the JavaBackEnd. The unix kernel probably drops
the data that's in the pipe when the writer process is killed or exits.
One way to ensure that the JavaBackEnd has read everything you sent, is
to actually implement what would be normal in a GUI application: an
event loop. If you wait for a mouse-down event on the window, then you
will ensure that all you sent has been received.
Also, you have a bug in your initBricks(), you set y to a constant in
the loop. Therefore all the new bricks beyond the first two rows will be
displayed on the second row.
[pjb@kuiper localhost:10.0 spl]$ make -f bricks.mk run-bricks
cc -g3 -O0 -std=c99 -std=c11 -o bricks.o -c bricks.c
cc -g3 -O0 -std=c99 -std=c11 -o bricks bricks.o -lcs -lm -lobjc
CLASSPATH=/usr/local/lib/spl.jar ./bricks
C-c C-c
Interrupted: exiting.
bricks.mk:14: recipe for target 'run-bricks' failed
make: *** [run-bricks] Interrupt
[pjb@kuiper localhost:10.0 spl]$
Here are my files:
------------------------------------------------------------------------
#!/bin/sh
# This is a shell archive (produced by GNU sharutils 4.14).
# To extract the files from this archive, save it to some FILE, remove
# everything before the '#!/bin/sh' line above, then type 'sh FILE'.
#
lock_dir=_sh18948
# Made on 2015-11-14 22:23 CET by <pjb@kuiper>.
# Source directory was '/home/pjb/src/miscellaneous/spl'.
#
# Existing files will *not* be overwritten, unless '-c' is specified.
#
# This shar contains:
# length mode name
# ------ ---------- ------------------------------------------
# 379 -rw-r--r-- bricks.mk
# 1527 -rw-r--r-- bricks.c
#
MD5SUM=${MD5SUM-md5sum}
f=`${MD5SUM} --version | egrep '^md5sum .*(core|text)utils'`
test -n "${f}" && md5check=true || md5check=false
${md5check} || \
echo 'Note: not verifying md5sums. Consider installing GNU coreutils.'
if test "X$1" = "X-c"
then keep_file=''
else keep_file=true
fi
echo=echo
save_IFS="${IFS}"
IFS="${IFS}:"
gettext_dir=
locale_dir=
set_echo=false
for dir in $PATH
do
if test -f $dir/gettext \
&& ($dir/gettext --version >/dev/null 2>&1)
then
case `$dir/gettext --version 2>&1 | sed 1q` in
*GNU*) gettext_dir=$dir
set_echo=true
break ;;
esac
fi
done
if ${set_echo}
then
set_echo=false
for dir in $PATH
do
if test -f $dir/shar \
&& ($dir/shar --print-text-domain-dir >/dev/null 2>&1)
then
locale_dir=`$dir/shar --print-text-domain-dir`
set_echo=true
break
fi
done
if ${set_echo}
then
TEXTDOMAINDIR=$locale_dir
export TEXTDOMAINDIR
TEXTDOMAIN=sharutils
export TEXTDOMAIN
echo="$gettext_dir/gettext -s"
fi
fi
IFS="$save_IFS"
if (echo "testing\c"; echo 1,2,3) | grep c >/dev/null
then if (echo -n test; echo 1,2,3) | grep n >/dev/null
then shar_n= shar_c='
'
else shar_n=-n shar_c= ; fi
else shar_n= shar_c='\c' ; fi
f=shar-touch.$$
st1=200112312359.59
st2=123123592001.59
st2tr=123123592001.5 # old SysV 14-char limit
st3=1231235901
if touch -am -t ${st1} ${f} >/dev/null 2>&1 && \
test ! -f ${st1} && test -f ${f}; then
shar_touch='touch -am -t $1$2$3$4$5$6.$7 "$8"'
elif touch -am ${st2} ${f} >/dev/null 2>&1 && \
test ! -f ${st2} && test ! -f ${st2tr} && test -f ${f}; then
shar_touch='touch -am $3$4$5$6$1$2.$7 "$8"'
elif touch -am ${st3} ${f} >/dev/null 2>&1 && \
test ! -f ${st3} && test -f ${f}; then
shar_touch='touch -am $3$4$5$6$2 "$8"'
else
shar_touch=:
echo
${echo} 'WARNING: not restoring timestamps. Consider getting and
installing GNU '\''touch'\'', distributed in GNU coreutils...'
echo
fi
rm -f ${st1} ${st2} ${st2tr} ${st3} ${f}
#
if test ! -d ${lock_dir} ; then :
else ${echo} "lock directory ${lock_dir} exists"
exit 1
fi
if mkdir ${lock_dir}
then ${echo} "x - created lock directory ${lock_dir}."
else ${echo} "x - failed to create lock directory ${lock_dir}."
exit 1
fi
# ============= bricks.mk ==============
if test -n "${keep_file}" && test -f 'bricks.mk'
then
${echo} "x - SKIPPING bricks.mk (file already exists)"
else
${echo} "x - extracting bricks.mk (text)"
sed 's/^X//' << 'SHAR_EOF' > 'bricks.mk' &&
all: bricks
X
LIBS=-lcs -lm -lobjc
CFLAGS=-g3 -O0 -std=c99 -std=c11
X
%.o:%.m;cc $(CFLAGS) -o $@ -c $^
%.o:%.c;cc $(CFLAGS) -o $@ -c $^
X
bricks.o:bricks.c
bricks:bricks.o
X cc $(CFLAGS) -o $@ $^ $(LIBS)
X
run-bricks:bricks
X CLASSPATH=/usr/local/lib/spl.jar ./bricks
X
debug-bricks:bricks
X JBETRACE=true CLASSPATH=/usr/local/lib/spl.jar ./bricks
X
clean:
X -rm -rf bricks *.dSYM *.o
X
SHAR_EOF
(set 20 15 11 14 22 22 21 'bricks.mk'
eval "${shar_touch}") && \
chmod 0644 'bricks.mk'
if test $? -ne 0
then ${echo} "restore of bricks.mk failed"
fi
if ${md5check}
then (
${MD5SUM} -c >/dev/null 2>&1 || ${echo} 'bricks.mk': 'MD5 check failed'
) << \SHAR_EOF
08f3fc95e6ba9bb115154029c5351a2d bricks.mk
SHAR_EOF
else
test `LC_ALL=C wc -c < 'bricks.mk'` -ne 379 && \
${echo} "restoration warning: size of 'bricks.mk' is not 379"
fi
fi
# ============= bricks.c ==============
if test -n "${keep_file}" && test -f 'bricks.c'
then
${echo} "x - SKIPPING bricks.c (file already exists)"
else
${echo} "x - extracting bricks.c (text)"
sed 's/^X//' << 'SHAR_EOF' > 'bricks.c' &&
// standard libraries
#include <stdio.h>
#include <signal.h>
// Stanford Portable Library
#include <spl/gevents.h>
#include <spl/gobjects.h>
#include <spl/gwindow.h>
#include <spl/platform.h>
X
// height and width of game's window in pixels
#define HEIGHT 600
#define WIDTH 400
X
// number of rows of bricks
#define ROWS 5
X
// number of columns of bricks
#define COLS 10
X
// horizontal space between bricks
#define HS 10
#define VS 10
X
// brick size
#define BRWIDTH 29
#define BRHEIGHT 15
X
void initBricks(GWindow window);
X
bool done=false;
bool interrupted=false;
void sigint(int signal){
X interrupted=true;
X done=true;}
X
void eventLoop(){
X while(!done){
X GEvent e=getNextEvent(MOUSE_EVENT);
X if(e!=0){
X if(getEventType(e)==MOUSE_CLICKED){
X done=true;}
X freeEvent(e);}}}
X
int main(void)
{
X signal(SIGINT,sigint);
X signal(SIGQUIT,sigint);
X GWindow window = newGWindow(WIDTH, HEIGHT);
X initBricks(window);
X eventLoop();
X if(interrupted){
X printf("\nInterrupted: exiting.\n");
X fflush(stdout);}
X exitGraphicsOp();
X return 0;
}
X
/** BRICKS FUNCTION **/
void initBricks(GWindow window)
{
X GRect brick;
X double y = VS * 5;
X for (int i = 0; i < ROWS; i++)
X {
X double x = 10;
X y = y + BRHEIGHT + VS;
X for (int j = 0; j < COLS; j++)
X {
X brick = newGRect(x, y, BRWIDTH, BRHEIGHT);
X add(window, brick);
X
X x = x + BRWIDTH + HS;
X }
X
X }
}
SHAR_EOF
(set 20 15 11 14 22 16 45 'bricks.c'
eval "${shar_touch}") && \
chmod 0644 'bricks.c'
if test $? -ne 0
then ${echo} "restore of bricks.c failed"
fi
if ${md5check}
then (
${MD5SUM} -c >/dev/null 2>&1 || ${echo} 'bricks.c': 'MD5 check failed'
) << \SHAR_EOF
2b8bed01642279076e0076c052d83adf bricks.c
SHAR_EOF
else
test `LC_ALL=C wc -c < 'bricks.c'` -ne 1527 && \
${echo} "restoration warning: size of 'bricks.c' is not 1527"
fi
fi
if rm -fr ${lock_dir}
then ${echo} "x - removed lock directory ${lock_dir}."
else ${echo} "x - failed to remove lock directory ${lock_dir}."
exit 1
fi
exit 0
------------------------------------------------------------------------
--
__Pascal Bourguignon__ http://www.informatimago.com/
“The factory of the future will have only two employees, a man and a
dog. The man will be there to feed the dog. The dog will be there to
keep the man from touching the equipment.” -- Carl Bass CEO Autodesk
[toc] | [prev] | [next] | [standalone]
| From | modelling.data@gmail.com |
|---|---|
| Date | 2015-11-15 00:10 -0800 |
| Message-ID | <5754f1d1-d921-4678-a88f-9c8432fd97e1@googlegroups.com> |
| In reply to | #205 |
<snip> > You should provide a makefile along with your program! Otherwise, how > can we know how to compile it, what options you used, and how to run it? > Yes, I understand it, that is why I have added a comment saying I understand that it wouldn't be possible to compile the program without SPL headers. I am new not only to Objective C, but to programming in general. I follow a free online course, that gives broad information, and I read books on my own and do some exercises. Therefore, I have not yet learned how to create makefiles. I am very thankful to you for the version you posted, though at this moment it look too cryptic from me. I have not yet learned debugging either. > Here is the makefile I used, but if yours is different, then obviously > we will have different results, and I won't be able to debug your > program. > > Also, you have a bug in your initBricks(), you set y to a constant in > the loop. Therefore all the new bricks beyond the first two rows will be > displayed on the second row. > Thank you very much - I am ashamed that I missed such an easy bug. Indeed, this one caused the problem. I have forgotten to add one tiny + sign before = one. >
[toc] | [prev] | [next] | [standalone]
| From | "Pascal J. Bourguignon" <pjb@informatimago.com> |
|---|---|
| Date | 2015-11-15 21:40 +0100 |
| Message-ID | <878u5z0zdx.fsf@kuiper.lan.informatimago.com> |
| In reply to | #207 |
modelling.data@gmail.com writes:
> <snip>
>> You should provide a makefile along with your program! Otherwise, how
>> can we know how to compile it, what options you used, and how to run it?
>>
> Yes, I understand it, that is why I have added a comment saying I understand
> that it wouldn't be possible to compile the program without SPL headers.
> I am new not only to Objective C, but to programming in general. I follow
> a free online course, that gives broad information, and I read books on my
> own and do some exercises. Therefore, I have not yet learned how to create
> makefiles. I am very thankful to you for the version you posted, though
> at this moment it look too cryptic from me. I have not yet learned debugging
> either.
Makefile are really simple really.
Basically, they allow you to indicate the dependency graph between
files, in the form:
target : source…
<TAB> command
or as an extension too:
target : source… ; command
You can also define variables:
VAR=VALUE
We can also specify default commands using patterns:
%.o:%.m;cc $(CFLAGS) -o $@ -c $^
is an example of such a pattern.
make knows a default set of patterns to compile simple programs.
There are some targets that don't correspond to files; they're called
phony targets, you can declare you own with:
.PHONY:: target…
all, clean are some of the default phony targets. The difference
between normal targets, is that they're not intended to generate files,
but instead will try to make their dependencies, and command everytime
they're invoked.
That's all there is to it.
So, to run-bricks, we need the program bricks; to compile the program
bricks we need the object file bricks.o and to compile the object file
bricks.o we need the source file bricks.c. This is expressed simply as:
run-bricks:bricks
bricks:bricks.o
bricks.o:bricks.c
As such, make would provide default rules, but I wanted to provide my
own rules, so I defined the pattern rule %.o:%.m to indicate how to
compile bricks.c into bricks.o, and I provided explicit commands to
indicate how to link bricks.o into bricks, and how to run the bricks
command for the phony target run-bricks.
There are extensions, in eg. GNU make, (which actually make it turing
complete, and allowed somebody to implement a lisp in GNU make), you can
find the GNU make documentation online.
all: bricks
LIBS=-lcs -lm -lobjc
CFLAGS=-g3 -O0 -std=c99 -std=c11
%.o:%.m;cc $(CFLAGS) -o $@ -c $^
%.o:%.c;cc $(CFLAGS) -o $@ -c $^
.PHONY::run-bricks debug-bricks
bricks.o:bricks.c
bricks:bricks.o
cc $(CFLAGS) -o $@ $^ $(LIBS)
run-bricks:bricks
CLASSPATH=/usr/local/lib/spl.jar ./bricks
debug-bricks:bricks
JBETRACE=true CLASSPATH=/usr/local/lib/spl.jar ./bricks
clean:
-rm -rf bricks *.dSYM *.o
>> Here is the makefile I used, but if yours is different, then obviously
>> we will have different results, and I won't be able to debug your
>> program.
>>
>
>> Also, you have a bug in your initBricks(), you set y to a constant in
>> the loop. Therefore all the new bricks beyond the first two rows will be
>> displayed on the second row.
>>
> Thank you very much - I am ashamed that I missed such an easy bug. Indeed,
> this one caused the problem. I have forgotten to add one tiny + sign before
> = one.
Just remember to use printf to display your variables when you're
debugging.
--
__Pascal Bourguignon__ http://www.informatimago.com/
“The factory of the future will have only two employees, a man and a
dog. The man will be there to feed the dog. The dog will be there to
keep the man from touching the equipment.” -- Carl Bass CEO Autodesk
[toc] | [prev] | [next] | [standalone]
| From | modelling.data@gmail.com |
|---|---|
| Date | 2015-11-17 07:30 -0800 |
| Message-ID | <aefa71a0-02de-4a94-a703-f16ba16f70e7@googlegroups.com> |
| In reply to | #209 |
<snip> Thank you very much for your help! I do appreciate it: studying on my own is a challenge, given lack of prior programming experience.
[toc] | [prev] | [next] | [standalone]
| From | "Pascal J. Bourguignon" <pjb@informatimago.com> |
|---|---|
| Date | 2015-11-14 22:47 +0100 |
| Message-ID | <87pozc1cfd.fsf@kuiper.lan.informatimago.com> |
| In reply to | #204 |
modelling.data@gmail.com writes:
> Hello!
>
> I have written a post regarding the same program.
>
> I have an issue with the easiest part of it, and I don't see
> my mistake: the for loop in the BRICKS FUNCTION doesn't create
> 5 rows of bricks, but only 2, albeit the amount of columns is correct
> (all bricks are perfectly aligned within 10 columns). The program
> prints out only 2 rows of bricks.
By the way, you will have noticed in my makefile the debug-bricks target
which runs your program with the environment variable JBETRACE set to
true. This allows you to see the traffic sent and received on the pipe
by your program (but you don't see what happens on the other side of the
pipe, data written in the pipe buffer is not necessarily read by the
other side). Nonetheless, this let you see what happens with the GUI
when you have doubts about what you program does.
You should be able to set it on and off using putenv(3):
putenv("JBETRACE=true");
putenv("JBETRACE=false");
if you want to trace only parts of your program.
Secondly, one big problem of batch programming environment such as the
usual C compilers, is that you don't see what's in your variables during
execution or debugging. Granted, you could run a debugger, but gdb or
ldb are low level debuggers, and while you may be able to see what's in
a variable or a data structure, it's rather difficult, and there are all
kinds of exception (notably when optimization levels are higher than 0
(notice the -g -O0 options I use to compile). Therefore, a very common
and useful technique while debugging, is to add to your program a lot of
logs displaying the values of your variables.
Adding a single line such as:
/** BRICKS FUNCTION **/
void initBricks(GWindow window)
{
double x = 10;
double y = VS * 5;
for (int i = 0; i < ROWS; i++)
{
for (int j = 0; j < COLS; j++)
{
/*PJB-DEBUG*/printf("i=%i j=%i x=%f y=%f w=%f h=%f\n",i,j,x, y, BRWIDTH, BRHEIGHT);
GRect brick = newGRect(x, y, BRWIDTH, BRHEIGHT);
add(window, brick);
x = x + BRWIDTH + HS;
}
x = 10;
y = BRHEIGHT + VS;
}
}
would allow you to easily see what one problem was. Notice the
/*PJB-DEBUG*/ comment. You can easily search and replace them to
//PJB-DEBUG to disable such lines, and use:
sed -i -e /PJB-DEBUG/d bricks.c
to remove them entirely once your program works.
--
__Pascal Bourguignon__ http://www.informatimago.com/
“The factory of the future will have only two employees, a man and a
dog. The man will be there to feed the dog. The dog will be there to
keep the man from touching the equipment.” -- Carl Bass CEO Autodesk
[toc] | [prev] | [next] | [standalone]
| From | modelling.data@gmail.com |
|---|---|
| Date | 2015-11-15 00:12 -0800 |
| Message-ID | <53011d76-3c8a-46e0-b542-fa417134c790@googlegroups.com> |
| In reply to | #206 |
<snip>
> for (int i = 0; i < ROWS; i++)
> {
> for (int j = 0; j < COLS; j++)
> {
>
> /*PJB-DEBUG*/printf("i=%i j=%i x=%f y=%f w=%f h=%f\n",i,j,x, y, BRWIDTH, BRHEIGHT);
>
> GRect brick = newGRect(x, y, BRWIDTH, BRHEIGHT);
> add(window, brick);
>
> x = x + BRWIDTH + HS;
> }
>
> x = 10;
> y = BRHEIGHT + VS;
> }
> }
>
> would allow you to easily see what one problem was. Notice the
> /*PJB-DEBUG*/ comment. You can easily search and replace them to
> //PJB-DEBUG to disable such lines, and use:
>
> sed -i -e /PJB-DEBUG/d bricks.c
>
> to remove them entirely once your program works.
Thank you for your advice. I will implement it.
[toc] | [prev] | [standalone]
Back to top | Article view | comp.lang.objective-c
csiph-web